<template>
  <div class="app-container">
    <div class="search-bar">
      <el-form ref="queryFormRef" :model="queryParams" :inline="true">
        <el-form-item prop="keywords" :label="$t('common.keywords')">
          <el-input
            v-model="queryParams.keywords"
            :placeholder="
              $t('visitor.name') + ', ' + $t('visitor.email') + ', ' + $t('visitor.phone')
            "
            clearable
            @keyup.enter="handleQuery"
          />
        </el-form-item>
        <el-form-item prop="opUserId" :label="$t('visitor.opName')">
          <el-autocomplete
            v-model="queryParams.opName"
            :fetch-suggestions="querySearch"
            clearable
            class="inline-input w-50"
            @select="handleSelect"
          />
        </el-form-item>
        <el-form-item prop="status" :label="$t('visitor.status')">
          <el-select
            v-model="queryParams.statuses"
            clearable
            multiple
            :placeholder="$t('common.choose')"
            :no-match-text="$t('common.choose')"
            style="width: 300px"
            @change="handleQuery"
          >
            <el-option :label="$t('visitor.bindStatus.0')" value="0" />
            <el-option :label="$t('visitor.bindStatus.1')" value="1" />
            <el-option :label="$t('visitor.bindStatus.2')" value="2" />
          </el-select>
        </el-form-item>
        <el-form-item>
          <el-button type="primary" icon="search" @click="handleQuery">
            {{ $t("common.search") }}
          </el-button>
          <el-button icon="refresh" @click="handleResetQuery">{{ $t("common.reset") }}</el-button>
        </el-form-item>
      </el-form>
    </div>

    <el-card shadow="never">
      <el-table ref="dataTableRef" v-loading="loading" :data="list" highlight-current-row stripe>
        <el-table-column :label="$t('visitor.name')" prop="visitorName" />
        <el-table-column :label="$t('visitor.email')" prop="email" />
        <el-table-column :label="$t('visitor.dept')" align="center" prop="deptName" />
        <el-table-column :label="$t('visitor.purpose')" align="center" prop="purposeName" />
        <el-table-column :label="$t('visitor.status')" align="center" prop="status">
          <template #default="scope">
            <el-tag v-if="scope.row.status === 0" type="info">
              {{ $t("visitor.bindStatus.0") }}
            </el-tag>
            <el-tag v-else-if="scope.row.status === 1" type="primary">
              {{ $t("visitor.bindStatus.1") }}
            </el-tag>
            <el-tag v-else-if="scope.row.status === 2" type="danger">
              {{ $t("visitor.bindStatus.2") }}
            </el-tag>
          </template>
        </el-table-column>
        <el-table-column :label="$t('visitor.planInAt')" prop="planInAt">
          <template #default="scope">
            {{ scope.row.planInAt ? dayjs(scope.row.planInAt).format("YYYY-MM-DD HH:mm:ss") : "" }}
            {{
              scope.row.planOutAt && !scope.row.planOutAt.includes("0001-01-01")
                ? " / " + dayjs(scope.row.planOutAt).format("YYYY-MM-DD HH:mm:ss")
                : ""
            }}
          </template>
        </el-table-column>
        <el-table-column :label="$t('visitor.actInAt')" prop="actInAt">
          <template #default="scope">
            {{
              scope.row.actInAt != null
                ? dayjs(scope.row.actInAt).format("YYYY-MM-DD HH:mm:ss")
                : ""
            }}
            {{
              scope.row.actOutAt != null
                ? " / " + dayjs(scope.row.actOutAt).format("YYYY-MM-DD HH:mm:ss")
                : ""
            }}
          </template>
        </el-table-column>
        <el-table-column :label="$t('visitor.tagNo')" align="center" prop="tagNo" />
        <el-table-column :label="$t('visitor.opName')" align="center" prop="opName" />
        <el-table-column :label="$t('common.createdAt')" prop="createdAt">
          <template #default="scope">
            {{ dayjs(scope.row.createdAt).format("YYYY-MM-DD HH:mm:ss") }}
          </template>
        </el-table-column>
        <el-table-column fixed="right" :label="$t('common.action')">
          <template #default="scope">
            <el-popconfirm
              v-if="scope.row.status == 0"
              :confirm-button-text="$t('common.confirm')"
              :cancel-button-text="$t('common.cancel')"
              :title="$t('common.confirmDelete') + '?'"
              @confirm="handleDelete(scope.row.id)"
            >
              <template #reference>
                <el-button
                  v-hasPerm="'visitor:share'"
                  type="danger"
                  size="small"
                  link
                  icon="Delete"
                >
                  {{ $t("common.delete") }}
                </el-button>
              </template>
            </el-popconfirm>
            <el-button
              v-if="scope.row.status == 0"
              v-hasPerm="'visitor:bind_tag'"
              type="primary"
              size="small"
              link
              icon="Link"
              @click="handleOpenDialog(scope.row.id)"
            >
              {{ $t("visitor.bindTag") }}
            </el-button>
            <el-button
              v-if="scope.row.status == 1"
              v-hasPerm="'visitor:unbind_tag'"
              type="info"
              size="small"
              link
              icon="Finished"
              @click="handleLeft(scope.row.id)"
            >
              {{ $t("visitor.unBindTag") }}
            </el-button>
          </template>
        </el-table-column>
      </el-table>

      <pagination
        v-if="total > 0"
        v-model:total="total"
        v-model:page="queryParams.pageNum"
        v-model:limit="queryParams.pageSize"
        @pagination="handleQuery"
      />
    </el-card>
    <el-dialog
      v-model="dialog.visible"
      :title="dialog.title"
      :width="dialogWidth"
      @close="handleCloseDialog"
    >
      <div>
        <div id="reader" style="position: absolute; z-index: 100; display: none; width: 100%" />
        <button v-if="isScanning" @click="stopScanning">{{ $t("common.stopScanning") }}</button>
      </div>
      <el-form ref="iFormRef" :model="formData" :rules="rules">
        <el-form-item :label="$t('visitor.tagNo')" prop="tagNo">
          <el-input
            v-model="formData.tagNo"
            :placeholder="$t('common.plsInput') + $t('visitor.tagNo')"
          >
            <template #suffix>
              <el-icon class="el-input__icon" type="primary">
                <Camera v-if="!isScanning" @click="startScanning" />
              </el-icon>
            </template>
          </el-input>
        </el-form-item>
      </el-form>

      <template #footer>
        <div class="dialog-footer">
          <el-button type="primary" @click="handleSubmit">{{ $t("common.confirm") }}</el-button>
          <el-button @click="handleCloseDialog">{{ $t("common.cancel") }}</el-button>
        </div>
      </template>
    </el-dialog>
  </div>
</template>

<script setup lang="ts">
import qrcodeScanSound from "@/assets/qrcodescan.mp3";
import { Html5Qrcode } from "html5-qrcode";
import Delete from "@/components/icons/Delete.vue";
import { ref } from "vue";
import dayjs from "dayjs";
import { useI18n } from "vue-i18n";
const { t } = useI18n();
defineOptions({
  name: "VisitorInviteList",
  inheritAttrs: false,
});

import VisitorAPI, { BindTagForm, IPageQuery, InvitePageVO } from "@/api/visitor/index";
const screenWidth = window.innerWidth;
const dialogWidth = screenWidth < 768 ? "90%" : "500px";
const queryFormRef = ref(ElForm);
const iFormRef = ref(ElForm);

const loading = ref(false);
const total = ref(0);

const isScanning = ref<boolean>(false);
const html5QrCode = ref<Html5Qrcode | null>(null);

const queryParams = reactive<IPageQuery>({
  pageNum: 1,
  pageSize: 10,
  keywords: "",
  statuses: ["0", "1", "2"],
  status: undefined,
});

const list = ref<InvitePageVO[]>();

const dialog = reactive({
  title: "",
  visible: false,
});

const formData = reactive<BindTagForm>({
  id: 0,
  tagNo: "",
});

const rules = reactive({
  tagNo: [{ required: true, message: t("common.plsInput") + t("visitor.tagNo"), trigger: "blur" }],
});

function handleQuery() {
  loading.value = true;
  VisitorAPI.getInviteList(queryParams)
    .then((data) => {
      list.value = data.list;
      total.value = data.total;
    })
    .finally(() => {
      loading.value = false;
    });
}

function handleResetQuery() {
  queryFormRef.value.resetFields();
  queryParams.pageNum = 1;
  handleQuery();
}

function handleOpenDialog(id?: number) {
  dialog.visible = true;
  dialog.title = t("visitor.bindTag");
  formData.id = id || 0;
}

function handleSubmit() {
  iFormRef.value.validate((valid: any) => {
    if (valid) {
      loading.value = true;
      VisitorAPI.bindTag(formData)
        .then((res) => {
          if (res.data.code === 200) {
            ElMessage.success(res.data.message);
            handleCloseDialog();
            handleResetQuery();
          } else {
            ElMessage.error(res.data.message);
          }
        })
        .finally(() => (loading.value = false));
    } else {
      console.log("error submit!!");
    }
  });
}

function handleCloseDialog() {
  dialog.visible = false;

  iFormRef.value.resetFields();
  iFormRef.value.clearValidate();

  formData.id = 0;

  setTimeout(() => {
    stopScanning();
  }, 100);
}

function handleLeft(id: number) {
  ElMessageBox.confirm(t("visitor.confirmLeft"), t("visitor.leftTip"), {
    confirmButtonText: t("common.confirm"),
    cancelButtonText: t("common.cancel"),
    type: "warning",
  }).then(() => {
    loading.value = true;
    VisitorAPI.unbindTag(id)
      .then((res) => {
        if (res.data.code === 200) {
          ElMessage.success(res.data.message);
          handleResetQuery();
        } else {
          ElMessage.error(res.data.message);
        }
      })
      .finally(() => (loading.value = false));
  });
}

const startScanning = () => {
  html5QrCode.value = new Html5Qrcode("reader");
  isScanning.value = true;

  const readerElement = document.getElementById("reader");
  if (readerElement) {
    readerElement.style.display = "block";
  }

  html5QrCode.value
    .start(
      { facingMode: "environment" },
      {
        fps: 20,
        qrbox: 250,
      },
      (decoded: string) => {
        playSound();
        formData.tagNo = decoded.slice(-6);
        stopScanning();
      },
      (err: any) => {
        isScanning.value = false;
      }
    )
    .catch((err: Error) => {
      isScanning.value = false;
    });
};

const stopScanning = () => {
  if (html5QrCode.value) {
    html5QrCode.value
      .stop()
      .then(() => {
        isScanning.value = false;
        html5QrCode.value = null;
        const readerElement = document.getElementById("reader");
        if (readerElement) {
          readerElement.style.display = "none";
        }
      })
      .catch((err: Error) => {});
  }
};

const playSound = () => {
  const audio = new Audio(qrcodeScanSound);
  audio.play().catch((error: Error) => {});
};

const handleDelete = (id: number) => {
  if (id === 0) return;
  VisitorAPI.deleteInvite(id)
    .then((res) => {
      if (res.data.code === 200) {
        ElMessage.success(res.data.message);
        handleResetQuery();
      } else {
        ElMessage.error(res.data.message);
      }
    })
    .finally(() => {});
};

interface RestaurantItem {
  value: string;
  opUserId: number;
}

const restaurants = ref<RestaurantItem[]>([]);
const querySearch = (queryString: string, cb: any) => {
  const results = queryString
    ? restaurants.value.filter(createFilter(queryString))
    : restaurants.value;
  // call callback function to return suggestions
  cb(results);
};
const createFilter = (queryString: string) => {
  return (restaurant: RestaurantItem) => {
    return restaurant.value.toLowerCase().indexOf(queryString.toLowerCase()) === 0;
  };
};
const loadAll = () => {
  const userList: RestaurantItem[] = [];
  VisitorAPI.getVisitorInviteListOpUserName().then((res) => {
    if (res != null) {
      res.forEach((user: any) => {
        userList.push({
          value: user.userFullName,
          opUserId: user.userId,
        });
      });
    }
  });
  return userList;
};

const handleSelect = (item: Record<string, any>) => {
  console.log(item.opUserId);
  queryParams.opUserId = item.opUserId;
};

onMounted(() => {
  handleQuery();
  restaurants.value = loadAll();
});
</script>
